import { defineStore } from 'pinia'
import { getNoopActions, injectState, useRemote, useWorker, wrapSafeActions } from '@/controller/base/index'
import type { Worker } from '@/controller/base/types/worker'
import type { Remote } from '@/controller/base/types/remote'
import type { BIWDController } from '../BIWD/definition'
import { BIWDActions, BIWDGetters, createBIWDState, useBIWDBinding } from '../BIWD/index'
import { DemoBaseActions, createDemoBaseState, setDemoBaseState } from './BaseAppliance'
import { merge } from 'lodash'
import type { DemoDatasource } from '@/demo/types'

let demoDatasource!: DemoDatasource

export function useDemoBIWDControl(): BIWDController.Control {
  const createDemoBIWDState: () => BIWDController.State = () =>
    injectState(
      () => merge(createBIWDState(), createDemoBaseState()),
      (state) => {
        setDemoBaseState(state, demoDatasource)
      }
    )
  const DemoBIWDGetters: BIWDController.Getters = {
    ...BIWDGetters,
  }
  const DemoBIWDActions: BIWDController.Actions = wrapSafeActions<BIWDController.Store, BIWDController.Actions>({
    ...merge(getNoopActions(BIWDActions), DemoBaseActions),
  })
  const useDemoStore = defineStore<'DemoBIWD', BIWDController.State, BIWDController.Getters, BIWDController.Actions>(
    'DemoBIWD',
    {
      state: createDemoBIWDState,
      getters: DemoBIWDGetters,
      actions: DemoBIWDActions,
    }
  )

  const store = useDemoStore() as BIWDController.Store
  const worker = useWorker(store) as Worker.ApplianceWorker<BIWDController.Store>
  const remote = useRemote(store) as Remote.ApplianceRemote<BIWDController.Store>
  return { store, worker, remote }
}

export function createDemoBIWDControl(datasource: DemoDatasource): BIWDController.Control {
  demoDatasource = datasource
  const control = useDemoBIWDControl()
  control.worker.init()
  useBIWDBinding(control)
  return control
}
